package com.leyou.item.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.leyou.common.dto.PageDTO;
import com.leyou.common.entity.Category;
import com.leyou.common.exception.LyException;
import com.leyou.item.entity.Sku;
import com.leyou.item.entity.Spu;
import com.leyou.item.entity.SpuDetail;
import com.leyou.item.mapper.SpuMapper;
import com.leyou.item.service.*;
import com.leyou.item.dto.SkuDTO;
import com.leyou.item.dto.SpuDTO;
import com.leyou.item.dto.SpuDetailDTO;
import lombok.extern.slf4j.Slf4j;
import org.springframework.amqp.core.AmqpTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

@Service
@Slf4j
public class SpuServiceImpl extends ServiceImpl<SpuMapper, Spu>implements SpuService {
   @Autowired
    private BrandService brandService;
   @Autowired
   private CategoryService categoryService;
   @Autowired
   private SkuService skuService;
   @Autowired
   private SpuDetailService spuDetailService;
   @Autowired
   private AmqpTemplate amqpTemplate;
    @Override
    public PageDTO<SpuDTO> pageQuery(Integer page, Integer rows, Boolean saleable, Long categoryId, Long brandId, Long id) {
       //分页条件对象
        Page<Spu>spuPage=new Page<>(page,rows);
        //执行分页查询及条件查询
        page(spuPage,new QueryWrapper<Spu>()
        .eq(saleable!=null,"saleable",saleable)
        .eq(null!=categoryId,"cid3",categoryId)
         .eq(null!=brandId,"brand_id",brandId)
                .eq(null!=id,"id",id)
        );
        List<SpuDTO>spuDTOS=SpuDTO.convertEntityList(spuPage.getRecords());
        for (SpuDTO spuDTO:spuDTOS){
            //TODO:根据分类id以及品牌id，查询对应的名称信息
            spuDTO.setBrandName(this.brandService.getById(spuDTO.getBrandId()).getName());

            //TODO List<Category>==>List<String>==>String names
            String names = this.categoryService.listByIds(spuDTO.getCategoryIds())
                    .stream()
                    .map(Category::getName)
                    .collect(Collectors.joining());
            spuDTO.setCategoryName(names);
        }
        return new PageDTO<>(spuPage.getTotal(),spuPage.getPages(),spuDTOS);
    }

    @Override
    @Transactional
    public void modifySaleable(Long id, Boolean saleable) {
            Spu spu=new Spu();
            spu.setId(id);
            spu.setSaleable(saleable);
            if (updateById(spu)){
                Sku sku=new Sku();
                sku.setSaleable(saleable);
                this.skuService.update(sku,new QueryWrapper<Sku>().eq("spu_id",id));
                String key=saleable ? "item.up" : "item.down";
                amqpTemplate.convertAndSend("heima107",key,id);
            }
    }

    @Override
    @Transactional
    public void addGoods(SpuDTO spuDTO) {
        Spu spu=spuDTO.toEntity(Spu.class);
        //保存spu 并主键回显
        if (save(spu)){
            SpuDetail spuDetail=spuDTO.getSpuDetail().toEntity(SpuDetail.class);
            spuDetail.setSpuId(spu.getId());
            //保存spuDetail
            this.spuDetailService.save(spuDetail);
            saveSkus(spuDTO.getSkus(), spu.getId());
        }
    }

    private void saveSkus(List<SkuDTO>skuDTOS, Long spuId) {
        //把skus的DTO形式转为entity形式
        List<Sku> skus=skuDTOS
                .stream()
                .map(skuDTO -> {
                    //把skuDTO转换为sku,并赋值spuId  并返回
                    Sku sku=skuDTO.toEntity(Sku.class);
                    sku.setSpuId(spuId);
                    return sku;
                }).collect(Collectors.toList());
        //批量保存sku
        this.skuService.saveBatch(skus);
    }

    @Override
    public SpuDTO queryGoodsBySpuId(Long id) {
        SpuDTO spuDTO=pageQuery(1,1,null,null,null,id).getItems().get(0);
        //把spuDetail 查询到后转换为spuDetaiDTO
        spuDTO.setSpuDetail(new SpuDetailDTO(this.spuDetailService.getById(id)));
        //根据spuId 查询对应的sku集合  并转为skuDTO
        spuDTO.setSkus(
                SkuDTO.convertEntityList(
                        this.skuService.query()
                        .eq("spu_id",id).list()));
        return spuDTO;
    }

    @Override
    @Transactional
    public void updateGoods(SpuDTO spuDTO) {
        //修改spu  修改spuDetail 修改sku
        //spu的id不为空
        if (null!=spuDTO.getId()){
            //修改spu
            if (updateById(spuDTO.toEntity(Spu.class))){
                log.info("spu修改成功");
            }else {
                log.error("spu修改失败");
                throw new LyException(500,"spu修改失败");
            }
            SpuDetailDTO spuDetailDTO=spuDTO.getSpuDetail();
            //修改spuDetail
            if (null!=spuDetailDTO){
                if (this.spuDetailService.updateById(spuDetailDTO.toEntity(SpuDetail.class))) {
                    log.info("spuDetail修改成功");
                }else {
                    log.error("spuDetail修改失败");
                }
                //sku修改  上架  下架  删除
                List<SkuDTO>skuDTOS=spuDTO.getSkus();
                List<SkuDTO>toAdd=new ArrayList<>();
                //循环遍历skuDTO集合找出要修改的直接修改  然后要新增的做新增处理
                for (SkuDTO skuDTO : skuDTOS) {
                    if (skuDTO.getId()==null){
                        toAdd.add(skuDTO);
                    }else {
                        this.skuService.updateById(skuDTO.toEntity(Sku.class));
                    }
                }
                if (0!=toAdd.size()){
                    //批量保存
                    saveSkus(toAdd,toAdd.get(0).getSpuId());
                }
            }
        }
    }
}
